﻿
using Dapper;
using HBase; 
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;

namespace hCommand
{
    public abstract class WcsFinshParamLocEngine<CS> : AbsLocEngine where CS : AbsCoreStock  {
        public long paramId;
        public int realStn;
        protected CoreTaskParam ctp;
        protected List<CoreTaskParam> otherCtpList;
        protected CoreTask ct;
        protected CS cs;

        protected virtual void doOther(IDbConnection conn, IDbTransaction tran) {
            foreach (CoreTaskParam o in otherCtpList) {
                if (o.src == ctp.src && o.des == TaskNoUtil.virtual_Loc) {
                    o.status = (int)CoreTaskParamStatus.执行完成;
                    string sql = @"update Core_Task_Param set  status=@status where id=@id";
                    conn.Execute(sql, o, tran);
                }
            }
        }

        protected override TransRes Execute(IDbConnection conn, IDbTransaction tran) {
            initData(conn, tran);
            int oldDes = ctp.des;

            if (realStn != 0) {
                ctp.des = realStn;
            }
            doOther(conn, tran);
            finshParam(conn, tran);
            UpdataWhLoc(conn, tran, (int)ctp.src, 0);//清除原货位 
            if (oldDes != realStn) {
                UpdataWhLoc(conn, tran, oldDes, 0);//清除原货位 
            }
    
            
            if (needFinsh(conn, tran)) {
                LocOrderUtil.finshCoreTask(conn, tran, ct.id);  
                if (I18nConfig.isLoc(ctp.des)) {
                    updateStockStatus(conn, tran, StockStatus.库存, ct.stockId);
                    UpdataWhLoc(conn, tran, ctp.des, cs.deepDiff);
                    inFinsh(conn, tran);
                } else {// if (I18nConfig.isLoc(ctp.src)) 
                    updateStockStatus(conn, tran, getOutTaskedStatus(conn, tran), ct.stockId);
                    UpdataWhLoc(conn, tran, ctp.des, cs.deepDiff);
                    outFinsh(conn, tran);
                }
            } else {
              
                if (isPk(conn, tran)) {
                    doPk(conn, tran);
                }
                UpdataWhLoc(conn, tran, ctp.des, cs.deepDiff);
            }   

            afterParamFinsh(conn, tran);
            return new TransRes();
        }
        protected virtual TransRes afterParamFinsh(IDbConnection connection, IDbTransaction transaction) {
            return new TransRes();
        }
       

        public virtual void doPk(IDbConnection conn, IDbTransaction tran) {
            if (ctp.des == ct.src) {
                LocOrderUtil.finshCoreTask(conn, tran, ct.id);
            }
        
        }



       void  updateStockStatus(IDbConnection conn, IDbTransaction tran,StockStatus status, long id) {
            exec(conn, tran, "update Core_stock set Status=@status   where id=@id and status="+ (int)StockStatus.移动中, new {
                id  ,
                status  
            });
        }
        public virtual void inFinsh(IDbConnection conn ,IDbTransaction tran) {

        }
        public virtual void outFinsh(IDbConnection conn ,IDbTransaction tran) {

        }


        void finshParam(IDbConnection conn ,IDbTransaction tran) {
            string sql = @"update Core_Task_Param set  status=" + ( int ) CoreTaskParamStatus.执行完成 + " where id=@id";
            conn.Execute(sql ,new { id = paramId } ,tran);


            if ( ctp.type != ( byte ) TaskParamType.机器人分解 ) {
                string updateSorestockSql = @"update Core_stock set  loc_Id=@stn, change_Time=sgj_get_sys_now where id=@id";
                conn.Execute(updateSorestockSql ,new { id = ct.stockId ,stn = ctp.des  } ,tran);

            } else {
                string updateSorestockSql = @"update Core_stock set   change_Time=sgj_get_sys_now where id=@id";
                conn.Execute(updateSorestockSql ,new { id = ct.stockId  } ,tran);


            }

        }

        
        void initData(IDbConnection connection ,IDbTransaction transaction) {
            string paramSql = "SELECT p1.*  FROM  [Core_Task_Param] p1  join [Core_Task_Param] p2 on p1.task_Id = p2.task_Id  where p2.id = " + paramId;
            otherCtpList = connection.Query<CoreTaskParam>(paramSql ,null ,transaction).ToList();
            foreach( CoreTaskParam p in otherCtpList ) {
                if( p.id == paramId ) {
                    ctp = p;
                    otherCtpList.Remove(p);
                    break;
                }
            }
            if( ctp == null ) {
                throw new Exception("任务参数不存在" + paramId);
            }
            ct = getById<CoreTask>(ctp.taskId ,connection ,transaction);
            cs = getById<CS>(ct.stockId,connection, transaction );
            
        }

        protected virtual TransRes afterFinsh(IDbConnection connection ,IDbTransaction transaction) {
            return new TransRes();
        }

        protected virtual bool needFinsh(IDbConnection conn ,IDbTransaction tran) {
            if (isPk(conn, tran)) {
                return false;
            }
            foreach ( CoreTaskParam ctp in otherCtpList ) {
                if( ctp.status < ( int ) CoreTaskParamStatus.执行完成 ) {
                    return false;
                }
            }

            return ct.des == ctp.des;
        }

        protected virtual  bool isPk(IDbConnection connection, IDbTransaction transaction) {
            return cs.status == (int)StockStatus.盘库中;
        }


        protected virtual StockStatus getOutTaskedStatus(IDbConnection connection ,IDbTransaction transaction) {
            return StockStatus.库外;
        }

   

    }
}
